#pragma once
#include <string>
#include <memory>
#include <cstring>
#include <iostream>
#include "global.h"
#include <netinet/in.h>

class MsgNode {
public:
    explicit MsgNode(size_t total_len)
        : _total_len(total_len), _cur_len(0)
    {
        // 分配 total_len + 1 字节，确保以 '\0' 结尾的安全空间
        _data = std::make_unique<char[]>(_total_len + 1);
        std::memset(_data.get(), 0, _total_len + 1);
    }

    virtual ~MsgNode() = default;

    void Clear() {
        if (_data) std::memset(_data.get(), 0, _total_len + 1);
        _cur_len = 0;
    }

    size_t _cur_len;       // 已使用长度
    size_t _total_len;     // 总长度
    std::unique_ptr<char[]> _data; // 数据缓冲区（唯一所有者）
};

// 接收消息类（含消息ID）
class RecvNode : public MsgNode {
public:
    RecvNode(size_t body_len, size_t msg_id)
        : MsgNode(body_len), _msg_id(msg_id) {}

    size_t _msg_id; // 消息ID
};

// 发送消息类（封装头部+体）
class SendNode : public MsgNode {
public:
    SendNode(const std::string& msg_body, size_t msg_id)
        : MsgNode(HEAD_TOTAL_LEN + msg_body.size()), _msg_id(msg_id)
    {
        uint16_t net_msg_id = htons(static_cast<uint16_t>(msg_id));
        uint16_t net_body_len = htons(static_cast<uint16_t>(msg_body.size()));

        std::memcpy(_data.get(), &net_msg_id, sizeof(net_msg_id));
        std::memcpy(_data.get() + 2, &net_body_len, sizeof(net_body_len));
        if (!msg_body.empty()) {
            std::memcpy(_data.get() + HEAD_TOTAL_LEN, msg_body.data(), msg_body.size());
        }
        _cur_len = _total_len;
    }

    size_t _msg_id; // 消息ID
};